home *** CD-ROM | disk | FTP | other *** search
/ Cream of the Crop 22 / Cream of the Crop 22.iso / program / asm32.zip / E32.ZIP / SEARCH.ASM < prev    next >
Assembly Source File  |  1996-08-26  |  7KB  |  361 lines

  1. ; SEARCH.ASM for E32 - Copyright (C) 1994 - 1996 Douglas Herr
  2. ;  all rights reserved
  3.  
  4. include    model.inc
  5.  
  6. ; 03/05/1996 DH: calls EDIT_STRING in UTIL.ASM
  7.  
  8. public    search, search_again, replace
  9.  
  10. extrn    locate:near
  11. extrn    working:near        ; 'Working' message
  12. extrn    display_screen:near, display_current:near
  13. extrn    close_space:near, open_space:near
  14. extrn    rowcount:near
  15. extrn    edit_string:near
  16.  
  17. extrn    strlen:near
  18. extrn    cursoron:near
  19. extrn    keyifwaiting:near, tprintce:near
  20. extrn    $strstr:near
  21. extrn    $stristr:near
  22.  
  23. include    dataseg.inc
  24.  
  25. public    replace_mode, kbdstat, called_by_menu
  26.  
  27. extrn    filesiz:dword        ; size of file
  28. extrn    search_start:byte    ; flag for top-of-file or cursor start
  29. extrn    search_text_buffer:byte, search_text_len:abs, string_edit_data:dword
  30.  
  31. extrn    cursor:dword, inverse:byte, rows:byte
  32. extrn    dirty_bits:byte
  33. extrn    zero_sel:dword
  34. extrn    first_row:byte
  35.  
  36. kbdstat    db 0
  37. find_mess    db " Find: ",0
  38. find_mess_len    equ    ($-find_mess)-1
  39. replace_msg    db ' replace? (Yes/No/All)',0
  40. replace_prompt    db ' Replace with: ',0
  41. replace_prompt_len    equ ($-replace_prompt)-1
  42. replace_mode    db 0
  43. called_by_menu    db 0
  44. search_len    dd 0
  45. replace_len    dd 0
  46. bytes_to_add    dw 0
  47. was_replaced    db 0
  48.  
  49. extrn    cur_posn:word
  50. extrn    breakflag:byte
  51. extrn    undo_length:word
  52. extrn    count_start:dword
  53. extrn    file_row:dword
  54. count_bytes    equ    dword ptr count_start+4
  55.  
  56. replace_text_len    equ 20
  57. replace_text_buffer    db (replace_text_len+1) dup(0)
  58.  
  59. @curseg    ends
  60.  
  61. include    codeseg.inc
  62. search_again    label proc
  63.     clc
  64.     call    save_offset        ; ret: EAX = cursor
  65.     mov    called_by_menu,0FFh    
  66.     jmp    short _ss0a
  67. ;
  68. ; This subroutine searches for a string
  69. ;
  70. search    proc    near
  71.     mov    es,zero_sel
  72.     mov    dl,es:[417h]        ; get kbd status
  73.     and    dl,11b            ; DL <> 0 if shift key pressed
  74.     jnz    replace            ; do REPLACE if SHIFT pressed
  75.  
  76.     clc
  77.     call    save_offset        ; save cursor offset
  78.                     ; ret: EAX = cursor
  79.     jc    exit
  80.  
  81.     cmp    [search_start],'c'    ; start at cursor?
  82.     je    short _ss0a
  83.     xor    eax,eax
  84.     mov    count_start,eax
  85.     mov    file_row,1
  86.     dec    eax
  87. _ss0a:
  88.     mov    dword ptr [search_start+1],eax
  89.     cmp    called_by_menu,0
  90.     jne    short s0
  91.  
  92. ; get search text if not called from menu
  93. _ss0b:
  94.     push    ds
  95.     pop    es
  96.     lea    edi,string_edit_data
  97.     lea    eax,search_text_buffer
  98.     stosd
  99.     mov    eax,search_text_len
  100.     stosd
  101.     lea    eax,find_mess
  102.     stosd
  103.     mov    eax,find_mess_len
  104.     stosd
  105.     call    edit_string
  106.  
  107.     cmp    ax,27
  108.     je    exit            ; exit if ESC pressed
  109.  
  110.     cmp    called_by_menu,0
  111.     jne    short s0
  112.     mov    kbdstat,dl        ; save keyboard status
  113.  
  114. s0:
  115.     lea    ebx,search_text_buffer
  116.     call    strlen
  117.     mov    search_len,ecx
  118.     jecxz    _ss0b
  119.     call    working            ; print 'Working' message
  120.  
  121.     mov    edi,dword ptr [search_start+1]
  122.     mov    esi,ebx
  123.     inc    edi            ; start search one past cursor
  124.     push    fs
  125.     pop    es
  126.     mov    ebx,ecx
  127.     mov    edx,filesiz
  128.     sub    edx,edi            ; bytes in file to search
  129.     jbe    short exit
  130.  
  131.     test    kbdstat,3        ; Shift key pressed?
  132.     jz    short s5
  133.     call    $stristr
  134.     jmp    short s6
  135. s5:
  136.     call    $strstr
  137. s6:
  138.     jc    short exit
  139.     add    eax,dword ptr [search_start+1]
  140.     inc    eax
  141.     mov    cursor,eax
  142.  
  143. ; save bytes to search for rows
  144.     mov    ecx,eax
  145.     sub    ecx,count_start
  146.     mov    count_bytes,ecx
  147.  
  148.     mov    dh,rows
  149.     sub    dh,first_row
  150.     shr    dh,1
  151.     add    dh,first_row
  152.     mov    esi,eax            ; cursor
  153.     call    locate
  154.     or    dirty_bits,1
  155.     call    rowcount
  156. exit:
  157.     mov    called_by_menu,0
  158.     clc
  159.     ret
  160.  
  161. search    endp
  162.  
  163.  
  164. replace_proc    equ    [ebp-4]
  165.  
  166. replace    proc    near
  167.     enter    4,0
  168.     clc
  169.     push    [cursor]
  170.     push    [count_start]
  171.     push    [file_row]
  172.  
  173.     mov    eax,cursor
  174.     cmp    [search_start],'c'    ; start at cursor?
  175.     je    short r0
  176.     xor    eax,eax
  177.     mov    count_start,eax
  178.     mov    file_row,1
  179. r0:
  180.     mov    [cursor],eax
  181.     call    save_offset
  182.  
  183. ; get string to find
  184. r2:
  185.     push    ds
  186.     pop    es
  187.     lea    edi,string_edit_data
  188.     lea    eax,search_text_buffer
  189.     stosd
  190.     mov    eax,search_text_len
  191.     stosd
  192.     lea    eax,find_mess
  193.     stosd
  194.     mov    eax,find_mess_len
  195.     stosd
  196.     call    edit_string
  197.  
  198.     cmp    ax,27
  199.     je    replace_exit        ; exit if ESC pressed
  200.  
  201. ; save keyboard shift status if not called from menu
  202.     cmp    called_by_menu,0
  203.     jne    short r2a
  204.     mov    kbdstat,dl        ; save keyboard status
  205.  
  206. r2a:
  207.     lea    edi,search_text_buffer
  208.     mov    ebx,edi
  209.     call    strlen
  210.     mov    search_len,ecx
  211.  
  212.     push    ds
  213.     pop    es
  214.     lea    edi,string_edit_data
  215.     lea    eax,replace_text_buffer
  216.     stosd
  217.     mov    eax,replace_text_len
  218.     stosd
  219.     lea    eax,replace_prompt
  220.     stosd
  221.     mov    eax,replace_prompt_len
  222.     stosd
  223.     call    edit_string
  224.  
  225.     cmp    ax,27
  226.     je    replace_exit        ; exit if ESC pressed
  227.  
  228.     cmp    called_by_menu,0
  229.     jne    short r2b
  230.     mov    replace_mode,dl        ; save keyboard status
  231.  
  232. r2b:
  233.     lea    ebx,replace_text_buffer
  234.     call    strlen
  235.     mov    replace_len,ecx
  236.     sub    ecx,search_len        ; bytes to add
  237.                     ; negative if file is shortened
  238.                     ; zero if len(search) = len(replace)
  239.     mov    eax,offset @curseg:same_length
  240.     jz    short r1a
  241.     mov    eax,offset @curseg:increase
  242.     jns    short r1a
  243.     mov    eax,offset @curseg:decrease
  244.     neg    cx
  245.  
  246. r1a:    mov    replace_proc,eax
  247.     mov    bytes_to_add,cx
  248.  
  249.     mov    breakflag,0        ; zero the ^C flag
  250.  
  251. r:
  252.     call    search_again        ; search for next occurance
  253.     test    dirty_bits,1        ; flag set if string found
  254.     jz    short replace_exit    ;  exit if not found
  255.     call    display_screen        ; update screen
  256.     mov    dx,cur_posn
  257.     call    cursoron
  258.     shr    breakflag,1
  259.     jc    short replace_exit
  260.     cmp    replace_mode,0
  261.     jne    short _replace_string
  262.     lea    esi,replace_msg
  263.     mov    dh,rows
  264.     inc    dh
  265.     xor    dl,dl
  266.     mov    ah,inverse
  267.     call    tprintce
  268. r3:    shr    breakflag,1
  269.     jc    short replace_exit
  270.     call    keyifwaiting
  271.     test    ax,ax
  272.     jz    r3
  273.     shr    ah,1            ; filter out extended keycodes
  274.     jc    r3
  275.     cmp    al,27
  276.     je    short replace_exit
  277.     and    al,0FFh-32        ; upper case
  278.     cmp    al,'Y'
  279.     je    short _replace_string
  280.     cmp    al,'N'
  281.     je    r
  282.     cmp    al,'A'
  283.     jne    r3
  284.     not    replace_mode        ; change to continuous
  285.                     ; & fall into _replace_string
  286. _replace_string:
  287.     call    [replace_proc]
  288.     call    display_current
  289.     and    dirty_bits,11111110b
  290.     jmp    r
  291.  
  292. replace_exit:
  293.     test    was_replaced,1
  294.     jz    short r_exit
  295.     mov    dh,rows
  296.     sub    dh,first_row
  297.     shr    dh,1
  298.     add    dh,first_row
  299.     mov    esi,cursor            ; cursor
  300.     call    locate
  301.     or    dirty_bits,1
  302.     jmp    short r9
  303.  
  304. ;
  305. ; nothing was replaced
  306. ;
  307. r_exit:
  308.     pop    [file_row]
  309.     pop    [count_start]
  310.     pop    [cursor]
  311.  
  312. r9:
  313.     clc
  314.     leave
  315.     ret
  316. replace    endp
  317.  
  318.  
  319.  
  320. ;
  321. ; replace search string at cursor
  322. ; called indirectly by replace_proc
  323. ;
  324. decrease:
  325. ; net file size decrease if len(search) > len(replace)
  326.     movzx    eax,bytes_to_add    ; remove EAX bytes from file
  327.     call    close_space
  328.     jmp    short same_length
  329.  
  330. increase:
  331. ; net file size increase if len(search) < len(replace)
  332.     movzx    eax,bytes_to_add
  333.     call    open_space
  334.  
  335. same_length:
  336. ; copy replacement string to file
  337.     lea    esi,replace_text_buffer
  338.     mov    ecx,replace_len
  339.     mov    edi,cursor
  340.     add    cursor,ecx
  341.     push    fs
  342.     pop    es
  343.     cld
  344.     rep    movsb
  345.     mov    was_replaced,1
  346.     or    dirty_bits,10000000b
  347.     ret
  348.  
  349.  
  350. ;
  351. ; save absolute cursor offset for count_start
  352. ;
  353. save_offset:
  354.     mov    eax,cursor
  355.     mov    count_start,eax
  356.     cld
  357.     ret
  358.  
  359. @curseg    ends
  360.     end
  361.